// TODO: CODE REVIEW & CLEANUP!
//
// MusicFoundTracksScreen.xaml.cs
//

using System;
using System.Diagnostics;
using System.Windows;
using System.Windows.Controls;
using System.Xml;
using HomeUX.ClientAppSupport;
using HomeUX.ClientControlSupport;
using HomeUX.Controls;
using HomeUX.Synchronization;
using HomeUX.Utilities;

namespace HomeUX.MusicClientLibrary
{

public partial class MusicFoundTracksScreen : UserControl
{
    MusicClientHelper _musicClientHelper;
    Style _musicTextStyle;

    bool _isDirty = true;
    string _find;

    /// <summary>
    /// A <n>String.Format</n>-style format string to use for <n>HeaderTextBlock</n>.  Initialized
    /// from the design-time text value of  <n>HeaderTextBlock</n>.
    /// </summary>
    string _headerFormatString;

    // query string -- set by a "caller" before navigating here
    public string Find
    {
        get
        {
            return _find;
        }
        set
        {
            _find = value;
            _isDirty = true;
        }
    }

    public MusicFoundTracksScreen()
    {
        InitializeComponent();

        // initialize <_headerFormatString>
        _headerFormatString = HeaderTextBlock.Text;

        Loaded += MusicFoundTracksScreen_Loaded;
        GotFocus += MusicFoundTracksScreen_GotFocus;
    }

    void MusicFoundTracksScreen_Loaded(object sender, RoutedEventArgs e)
    {
        _musicClientHelper = new MusicClientHelper(this, BeginLoadingDataFromMusicServer,
            OnParcelReceived);

        _musicTextStyle = (Style)LayoutRoot.Resources["MusicTextStyle"];

        _musicClientHelper.Screen.Opened += OnScreenOpened;
    }

    void OnScreenOpened(object sender, EventArgs e)
    {
        // if the required properties were not set correctly before navigating to this screen,
        // this screen is in an error state
        if (Find == null)
        {
            _musicClientHelper.SetErrorState();
            return;
        }

        if (_isDirty)
        {
            HeaderTextBlock.Text = String.Format(_headerFormatString, Find,
                _musicClientHelper.MusicDeviceName);

            // do the same thing we'd do if we were waiting for the music server to become available
            _musicClientHelper.TryToLoadData();
        }
    }

    void BeginLoadingDataFromMusicServer()
    {
        TracksListBox.Items.Clear();

        string command = ParsedSyncNodeCommand.Format("Search",
             "RecipientId", XmlConvert.ToString(_musicClientHelper.RecipientId),
             "Find", Find,
             "MaxArtists", "-1",
             "MaxAlbums", "-1",
             "MaxTracks", "9999");

        _musicClientHelper.MusicDeviceNode.ExecuteCommand(command);
    }

    void OnParcelReceived(Guid recipientId, XmlReader reader)
    {
        try
        {
            foreach (XmlElementInfo element in XmlElementInfo.EnumerateElements(reader))
            {
                switch (element.Name)
                {

                case "FoundTrack":

					AddTrackToList(
                        element.GetRequiredAttribute("AlbumId"),
                        element.GetRequiredIntAttribute("TrackNumber"),
                        element.GetRequiredAttribute("ArtistName"),
                        element.GetRequiredAttribute("AlbumName"),
                        element.GetRequiredAttribute("TrackName"));
					break;

                case "/DoneSearch":

                    _musicClientHelper.OnDataLoaded();
                    _isDirty = false;
                    break;

                }
            }
        }
        catch (InvalidOperationException ex)
        {
            ClientGlobals.Alert(AlertType.Warning,
                "Invalid reply from server: {0}", ex.Message);
        }
    }

    /// <summary>
    /// Called when the request begun by <r>RequestTracks</r> has completed.  This method is
    /// called once for each artist.
    /// </summary>
    void AddTrackToList(string albumId, int trackNumber, string artistName, string albumName,
        string trackName)
    {
        var textBlock = new TextBlock()
        {
            Text = String.Format("{0} - {1} - {2}", trackName, albumName, artistName),
            Tag = new TrackId()
            {
                AlbumId = albumId,
                TrackNumber = trackNumber
            },
            Style = _musicTextStyle
        };
        TracksListBox.Items.Add(textBlock);
    }

    void MusicFoundTracksScreen_GotFocus(object sender, RoutedEventArgs e)
    {
        TracksListBox.Focus();
    }

    private void TracksListBox_ItemClick(object sender, ItemClickEventArgs e)
    {
        TrackId trackId = (TrackId)((TextBlock)e.Item).Tag;

        Screen screen;
        MusicAlbumScreen screenControl;
        _musicClientHelper.FindMusicScreen("Album", out screen, out screenControl);
        screenControl.AlbumId = trackId.AlbumId;
        screenControl.HighlightTrackNumber = trackId.TrackNumber;
        screen.GoTo();
    }

    // nested types

    [DebuggerDisplay("{AlbumId} {TrackNumber}")]
    public class TrackId
    {
        public string AlbumId;
        public int TrackNumber;
    }

}

}

